/*
 * 对象
 * */
define(function(){
	var objecter = {
		// 对象类型
		_types : {
			'[object Boolean]': 'boolean',
			'[object Number]': 'number',
			'[object String]': 'string',
			'[object Function]': 'function',
			'[object Array]': 'array',
			'[object Date]': 'date',
			'[object RegExp]': 'regExp',
			'[object Object]': 'object',
			'[object Null]': 'null',
			'[object Undefined]': 'undefined'
		},

		/**
		 * 检测v的类型
		 * @param {Any} v 被检测的变量
		 * @return {String}
		 */
		_type : function(v){
			return Object.prototype.toString.call(v);
		},

		/**
		 * 是否为字符串类型 如果是就返回true 如果不是就返回false
		 * @param {Any} v 被检测的变量
		 * @return {Boolean}
		 */
		isString : function(v){
			return typeof v === 'string';
		},

		/**
		 * 是否为数字类型(为Number且不为正负无穷大数字) 如果是就返回true 如果不是就返回false
		 * @param {Any} v 被检测的变量
		 * @return {Boolean}
		 */
		isNumber : function(v){
			return typeof v === 'number' && isFinite(v);
		},

		/**
		 * 是否为布尔值类型  如果是就返回true 如果不是就返回false
		 * @param {Any} v 被检测的变量
		 * @return {Boolean}
		 */
		isBoolean : function(v){
			return typeof v === 'boolean';
		},

		/**
		 * 是否为正则表达式类型  如果是就返回true 如果不是就返回false
		 * @param {Any} v 被检测的变量
		 * @return {Boolean}
		 */
		isRegexp : function(v){
			return this._type(v) === '[object RegExp]';
		},

		/**
		 * 是否为函数类型 如果是就返回true 如果不是就返回false
		 * @param {Any} v 被检测的变量
		 * @return {Boolean}
		 */
		isFunction : function(v){
			return this._type(v) === '[object Function]';
		},

		/**
		 * 是否为数组对象类型  如果是就返回true 如果不是就返回false
		 * @method isArray
		 * @param {Any} v 被检测的变量
		 * @return {Boolean} 结果
		 */
		isArray : function(v){
			return this._type(v) === '[object Array]';
		},

		/**
		 * 是否为对象类型
		 * @param {Any} v 被检测的变量
		 * @return {boolean}
		 */
		isObject : function(v){
			return !!v && typeof v === 'object';
		},

		/**
		 * 是否为纯对象类型
		 * @param {Any} v 被检测的变量
		 * @return {boolean}
		 */
		isPlainObject : function(v){
			return !!v && this._type(v) === '[object Object]';
		},

		/**
		 * 是否为null
		 * @param {Any} v 被检测的变量
		 * @return {boolean}
		 */
		isNull : function(v){
			return null === null && this._type(v) === '[object Null]';
		},

		/**
		 * 是否为日期类型  如果是就返回true 如果不是就返回false
		 * @param {Any} v 被检测的变量
		 * @return {boolean}
		 */
		isDate : function(v){
			return this._type(v) === '[object Date]';
		},

		/**
		 * 是否为空对象 null和undefined和数组的长度为0或空字符串("") 如果是就返回true 如果不是就返回false
		 * @param {Any} v 被检测的变量
		 * @param {Boolean} allowBlank [可选] 默认false 空字符串认为是空对象 反之 空字符串不认为是空对象
		 * @return {Boolean}
		 */
		isEmpty : function(v, allowBlank){
			return v === null || v === undefined ||
				(this.isArray(v) && !v.length) ||
				(!allowBlank ? v === '' : false);
		},

		/**
		 * 是否为空对象 null和undefined和数组的长度为0或空字符串("") 如果是就返回true 如果不是就返回false
		 * @param {Any} v 被检测的变量
		 * @param {Boolean} allowBlank [可选] 默认false 空字符串认为是空对象 反之 空字符串不认为是空对象
		 * @return {Boolean}
		 */
		IsNullOrEmpty: function (obj) {
			var flag = false;
			if (obj == null || obj == undefined || typeof (obj) == 'undefined' || obj == '') {
				flag = true;
			} else if (typeof (obj) == 'string') {
				obj = obj.trim();
				if (obj == '') {//为空
					flag = true;
				} else {//不为空
					obj = obj.toUpperCase();
					if (obj == 'NULL' || obj == 'UNDEFINED' || obj == '{}') {
						flag = true;
					}
				}
			}
			else {
				flag = false;
			}
			return flag;
		},

		/**
		 * 是否为参数管理器Arguments 如果是就返回true 如果不是就返回false
		 * @param {Any} v 被检测的变量
		 * @return {Boolean}
		 */
		isArguments : function(v){
			return v.callee !== undefined;
		},

		/**
		 * 是否为迭代序列 包含Array与Arguments 如果是就返回true 如果不是就返回false
		 * @param {Any} v 被检测的变量
		 * @return {Boolean}
		 */
		isIterable : function(v){
			return this.isArray(v) || this.isArguments(v);
		},

		/**
		 * 是否为原始数据类型 如果是就返回true 如果不是就返回false
		 * @param {Any} v 被检测的变量
		 * @return {Boolean}
		 */
		isPrimitive : function(v){
			return this.isString(v) || this.isNumber(v) ||
				this.isBoolean(v);
		},

		/**
		 * 是否为window 如果是就返回true 如果不是就返回false
		 * @param {Any} v 被检测的变量
		 * @return {Boolean}
		 */
		isWindow : function(v) {
			return v && typeof v === "object" && "setInterval" in v;
		},

		/**
		 * 是否为DOM元素
		 * @param {Any} v 被检测的变量
		 * @return {Boolean}
		 */
		isDOM : function(v){
			var func = ( typeof HTMLElement === 'object' ) ?
				function(obj){
					return obj instanceof HTMLElement;
				} :
				function(obj){
					return obj && typeof obj === 'object' && obj.nodeType === 1 && typeof obj.nodeName === 'string';
				}

			return func(v);
		},

		/**
		 * 是否为DOM元素节点
		 * @param {Any} v 被检测的变量
		 * @return {Boolean}
		 */
		isElementNode : function(node){
			return node && node.nodeType === 1;
			/*
			 节点类型	nodeType属性值
			 元素节点	1
			 属性节点	2
			 文本节点	3
			 */
		},

		/**
		 * 继承
		 * @param {Boolean} b 是否深复制
		 * @return {Object} arg1 复制的对象1
		 * @return {Object} arg2 复制的对象2
		 */
		extend : function(b, arg1, arg2){
			var options, name, src, copy, copyIsArray, clone,
				target = arguments[0] || {},
				i = 1,
				length = arguments.length,
				deep = false;

			if ( typeof target === "boolean" ) {
				deep = target;
				target = arguments[1] || {};
				i = 2;
			}

			if ( typeof target !== "object" && !this.isFunction(target) ) {
				target = {};
			}

			if ( length === i ) {
				target = this;
				--i;
			}

			for ( ; i < length; i++ ) {
				options = arguments[ i ];
				if ( options !== null && this.isObject(options) && !this.isDOM(options) && !this.isElementNode(options)) {
					for ( name in options ) {
						src = target[ name ];
						copy = options[ name ];
						if ( target === copy ) {
							continue;
						}
						if ( deep && copy && ( this.isPlainObject(copy) || (copyIsArray = this.isArray(copy)) ) ) {
							if ( copyIsArray ) {
								copyIsArray = false;
								clone = src && this.isArray(src) ? src : [];
							} else {
								clone = src && this.isPlainObject(src) ? src : {};
							}
							target[ name ] = this.extend( deep, clone, copy );
						} else if ( copy !== undefined ) {
							target[ name ] = copy;
						}
					}
				}
			}
			return target
		},

		//克隆
		clone : function (obj){
			var o;
			switch(typeof obj){
				case 'undefined': break;
				case 'string'   : o = obj + '';break;
				case 'number'   : o = obj - 0;break;
				case 'boolean'  : o = obj;break;
				case 'object'   :
					if(obj === null){
						o = null
					}else{
						if(obj instanceof Array){
							o = []
							for(var i = 0, len = obj.length; i < len; i++){
								o.push(this.clone(obj[i]))
							}
						}else{
							o = {};
							for(var k in obj){
								o[k] = this.clone(obj[k])
							}
						}
					}
					break
				default:
					o = obj;break
			}
			return o
		},

		/*
		* 遍历
		*/
		forEach : function (obj, func) {
			if (this.isArray(obj)) {
				for (var i = 0; i < obj.length; i++) {
					var b = func(obj[i], i, obj)
					if (b === false) {
						break
					}
				}
			} else if (this.isString(obj)) {
				var n = 0
				for (var item in obj) {
					var b = func(obj[item], n, obj)
					n += 1
					if (b === false) {
						break
					}
				}
			} else if (typeof obj === 'object' && obj !== null) {
				for (var property in obj) {
					if (obj.hasOwnProperty(property)) {
						var b = func(obj[property], property, obj)
						if (b === false) {
							break
						}
					}
				}
			}
		}
	}

	return objecter
})